﻿/*****************************************************************//**
 * \file   Tokenizer.h
 * \brief  Tokenizer 类负责将输入代码字符串分解为一系列的Token。
 *         它使用 IToken 接口和相关的具体Token类来创建和管理Token列表。
 *
 * \author 郝学胜
 * \date   2025-08-18
 *********************************************************************/
#pragma once
#include <vector>
#include <fstream>

#include "Token.h"

namespace Pomian
{
    /**
     * \brief Tokenizer 类用于将代码字符串分解为Token列表。
     */
    class TOKENIZER_EXPORT Tokenizer
    {
    private:
        int m_lineNumber; /**< 当前处理的行号。 */
        int m_tokenNumber; /**< 当前处理的Token编号。 */
        int m_doNumber; /**< 执行次数计数器。 */
        std::ifstream m_stream;
        std::vector<IToken*> m_tokens; /**< 存储生成的Token列表。 */

        std::vector<IToken*> tokenize(int lineNumber, const std::string& code); /**< 将单行代码分解为Token列表。 */

    public:
        /**
         * \brief Tokenizer的构造函数。
         * \param codes 输入的代码行列表。
         */
        Tokenizer(const std::string& filename);

        /**
         * \brief 记录执行词法分析。
         */
        void redo();

        /**
         * \brief 撤销上一步的词法分析，恢复到前一个状态。
         */
        void undo();

        /**
         * \brief 检查是否存在指定编号的Token。
         * \param number 要检查的Token编号。
         * \return 如果存在指定编号的Token，返回true；否则返回false。
         */
        bool has(int number);

        /**
         * \brief 移动到指定编号的Token。
         * \param number 要移动到的Token编号。
         */
        void move(int number);

        /**
         * \brief 获取当前指定索引的Token。
         * \param index 要获取的Token的索引。
         * \return 当前指定索引的Token指针。
         */
        IToken* current(int index);
    };
}